﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Media.Imaging;
using System.Windows.Shapes;
using System.Threading;
using Common.DataTypes;
using LinqAmazonProvider;
using System.Windows.Threading;
using System.Text.RegularExpressions;
using LinqToAmazonSilverlightUI.DataTypesUI;
using LinqToAmazonSilverlightUI;
using System.Text;
using System.Xml;
using System.IO;
using System.Xml.Serialization;
using System.Globalization;

namespace LinqToAmazonSilverlightUI
{
    public partial class Page : UserControl
    {
        private static ManualResetEvent Alldone;
        private static bool validKey;
        private Dictionary<int, string> languageTranslator = new Dictionary<int, string>();
        private Dispatcher _mainDispatcher;
        private List<Common.DataTypes.Book> lstQueryResult = new List<Book>();
        private DTSearchCriteria advanced;
        private int language;
        private string passwordAmazon;
        private Boolean passwordChanged;
        private Boolean newSearch;
        private int totalPages;
        private int actualPage;
        private int totalItems;
        private TextLanguage textL;
        private Boolean showItemInfo;

        const int ITEMS_PER_PAGE = 5;
        
        public DTSearchCriteria SearchCriteria { get; set; }

        public Page()
        {
            InitializeComponent();

            this.Loaded += (object sender, RoutedEventArgs e) => { anims.Begin(); };

            BrdLayoutRoot.Visibility = Visibility.Collapsed;
            BaseLayoutRoot.Visibility = Visibility.Collapsed;
            icMoreInfoPopUp.Visibility = Visibility.Collapsed;
            PopUpKey.Visibility = Visibility.Visible;
            passwordAmazon = "";
            passwordChanged = true;
            Popup();
            Show();

            this._mainDispatcher = MainDispatcher.Current;

            advanced = new DTSearchCriteria();

            //Initialize variables paged
            actualPage = 1;
            totalPages = 1;

            renderBigger.Completed += (s, ev) =>
            {
                renderBigger.Pause();

                // Case the storyboard is still executing on other button, it's stoped
                renderLower.Stop();
                renderLower.Begin();
            };
            renderLower.Completed += (s, ev) =>
            {
                renderLower.Pause();

                // Case the storyboard is still executing on other button, it's stoped
                renderBigger.Stop();
                renderBigger.Begin();
            };
            renderBigger.Begin();

            //By default: English
            textL = new TextLanguage();
            language = 1;
            SetLanguage();

            // Load language dictionary
            languageTranslator.Add(1, "ingles");
            languageTranslator.Add(2, "espaniol");
        }

        #region Search Functions

        void SearcherFnc()
        {
            PopUpKey.Visibility = Visibility.Collapsed;
            PopUpBox.Visibility = Visibility.Collapsed;
            PopUpLoading.Visibility = Visibility.Visible;
            Popup();
            Show();
            SBLoad.Begin();

            try
            {
                // Create thread to perform the amazon search
                Thread worker = new Thread(new ThreadStart(GetLINQResult));

                // Set the search parameters SearchCriteria = advanced;
                SearchCriteria = advanced; //searchKeyword = keyword;
                worker.Start();
            }
            catch (ThreadStateException ex)
            {
                lblExcep.Text = ex.Message;
                PopUpLoading.Visibility = Visibility.Collapsed;
                PopUpKey.Visibility = Visibility.Collapsed;
                PopUpBox.Visibility = Visibility.Collapsed;
                PopUpExcep.Visibility = Visibility.Visible;
                Popup();
                Show();
            }
            catch (OutOfMemoryException ex)
            {
                lblExcep.Text = ex.Message;
                PopUpLoading.Visibility = Visibility.Collapsed;
                PopUpKey.Visibility = Visibility.Collapsed;
                PopUpBox.Visibility = Visibility.Collapsed;
                PopUpExcep.Visibility = Visibility.Visible;
                Popup();
                Show();
            }
        }

        private void GetLINQResult()
        {
            try
            {
                List<Book> result = new List<Book>();

                // Create provider, set the Amazon key and language
                var provider = new AmazonProvider();
                provider.AmazonKey = passwordAmazon;
                provider.ResultLanguage = languageTranslator[language];

                var queryable = new AmazonQuery<Book>(provider);

                int numberItemsToSkip = ITEMS_PER_PAGE * (actualPage - 1);
                if (SearchCriteria.IsAdvanced)
                {
                    #region Advanced Search
                    int minPrice = decimal.ToInt32(SearchCriteria.MinPrice) * 100;
                    int maxPrice = decimal.ToInt32(SearchCriteria.MaxPrice) * 100;
                    string bookCondition = SearchCriteria.Condition;

                    var query =
                        from book in queryable
                        where
                          book.Author == SearchCriteria.Author && book.Publisher == SearchCriteria.Publisher &&
                          book.Title == SearchCriteria.Title && book.Condition == bookCondition && book.Category == SearchCriteria.Category &&
                          book.ListPrice.Amount >= minPrice && book.ListPrice.Amount <= maxPrice &&
                          book.Keywords == SearchCriteria.Keywords
                        select book;

                    if (SearchCriteria.SortBy.IsSortConditionSelected)
                    {
                        #region Add Sort Criteria
                        switch (SearchCriteria.SortBy.FirstSortCondition)
                        {
                            case DTSearchCriteria.Ascending:
                                query = query.OrderBy("ListPrice", false);
                                break;
                            case DTSearchCriteria.Descending:
                                query = query.OrderBy("ListPrice", true);
                                break;
                            case DTSearchCriteria.PubDate:
                                query = query.OrderBy("PublicationDate", false);
                                break;
                            case DTSearchCriteria.Tit:
                                query = query.OrderBy("Title", false);
                                break;
                        }

                        if (SearchCriteria.SortBy.IsSecondConditionSelected)
                        {
                            switch (SearchCriteria.SortBy.SecondSortCondition)
                            {
                                case DTSearchCriteria.Ascending:
                                    query = query.OrderBy("ListPrice", false);
                                    break;
                                case DTSearchCriteria.Descending:
                                    query = query.OrderBy("ListPrice", true);
                                    break;
                                case DTSearchCriteria.PubDate:
                                    query = query.OrderBy("PublicationDate", false);
                                    break;
                                case DTSearchCriteria.Tit:
                                    query = query.OrderBy("Title", false);
                                    break;
                            }
                        }

                        if (SearchCriteria.SortBy.IsThirdConditionSelected)
                        {
                            switch (SearchCriteria.SortBy.ThirdSortCondition)
                            {
                                case DTSearchCriteria.Ascending:
                                    query = query.OrderBy("ListPrice", false);
                                    break;
                                case DTSearchCriteria.Descending:
                                    query = query.OrderBy("ListPrice", true);
                                    break;
                                case DTSearchCriteria.PubDate:
                                    query = query.OrderBy("PublicationDate", false);
                                    break;
                                case DTSearchCriteria.Tit:
                                    query = query.OrderBy("Title", false);
                                    break;
                            }
                        }

                        #endregion
                    }
                    if (newSearch)
                    {
                        totalItems = query.Count<Book>();
                    }

                    query = query.Skip<Book>(numberItemsToSkip).Take<Book>(ITEMS_PER_PAGE);

                    result = query.ToList<Book>();
                    #endregion
                }
                else
                {
                    #region Normal Search
                    
                    var query =
                    from book in queryable
                     where
                       book.Keywords == SearchCriteria.MainKeywords
                     select book;

                    if (newSearch)
                    {
                        // If performing a new search, set the total items of response
                        totalItems = query.Count<Book>();
                    }

                    // Take only the items who belong to selected page
                    query = query.Skip<Book>(numberItemsToSkip).Take<Book>(ITEMS_PER_PAGE);

                    result = query.ToList<Book>();
                    #endregion
                }

                //Invoque the event on the UiThread to handle the response

                //Invoque the event on the UiThread
                _mainDispatcher.BeginInvoke(delegate()
                {
                    // Invoque search completed method
                    SearchCompleted(result);
                });
            }
            catch (ArgumentNullException e)
            {
                //TODO:: ver de hacer manejo de la excepcion o sacar
                lblExcep.Text = e.Message;
                PopUpLoading.Visibility = Visibility.Collapsed;
                PopUpKey.Visibility = Visibility.Collapsed;
                PopUpBox.Visibility = Visibility.Collapsed;
                PopUpExcep.Visibility = Visibility.Visible;
                Popup();
                Show();                
            }
        }

        private void SearchCompleted(IEnumerable<Book> query)
        {
            lstResult.ItemsSource = query;
            if (newSearch)
            {
                if (lstResult.Items.Count > 0)
                {
                    lstResult.Visibility = Visibility.Visible;
                    hlnkAdvSearch.Foreground = new SolidColorBrush(Colors.Black);
                }
                else
                {
                    lstResult.Visibility = Visibility.Collapsed;
                    hlnkAdvSearch.Foreground = new SolidColorBrush(Colors.White);
                }
                InitializePagesInformation();
            }

            SBLoad.Pause();
            btnLoadingMessage_Click(null, null);
            SBLoad.Stop();
            btnCloseMessage.Visibility = Visibility.Visible;
            PopUpBox.Visibility = Visibility.Visible;
            PopUpLoading.Visibility = Visibility.Collapsed;
        }

        void Search_Click(object sender, EventArgs args)
        {
            advanced.IsAdvanced = (uctrlAdvSearch.Visibility == Visibility.Visible);

            newSearch = true;
            actualPage = 1;
            totalPages = 1;
            totalItems = 0;
            if (advanced.IsAdvanced)
            {
                advanced.Author = uctrlAdvSearch.GetAuthor;
                advanced.Title = uctrlAdvSearch.GetTitle;

                advanced.Category = uctrlAdvSearch.GetCategory;

                advanced.Condition = uctrlAdvSearch.GetCondition;

                advanced.MaxPrice = uctrlAdvSearch.GetMaxPrice;

                advanced.MinPrice = uctrlAdvSearch.GetMinPrice;

                advanced.Publisher = uctrlAdvSearch.GetPublisher;
                advanced.Keywords = uctrlAdvSearch.GetKeyword;

                advanced.SortBy.IsSortConditionSelected = (uctrlAdvSearch.GetSortFirst != 0);
                advanced.SortBy.FirstSortCondition = uctrlAdvSearch.GetSortFirst;

                advanced.SortBy.IsSecondConditionSelected = (uctrlAdvSearch.GetSortSecond != 0);
                advanced.SortBy.SecondSortCondition = uctrlAdvSearch.GetSortSecond;

                advanced.SortBy.IsThirdConditionSelected = (uctrlAdvSearch.GetSortThird != 0);
                advanced.SortBy.ThirdSortCondition = uctrlAdvSearch.GetSortThird;

                uctrlAdvSearch.Visibility = Visibility.Collapsed;
                txtQuery.Visibility = Visibility.Visible;
                txtQuery.Text = uctrlAdvSearch.txtFilKeyword.Text;
                string Aux = ((string)hlnkAdvSearch.Content);
                hlnkAdvSearch.Content = hlnkAdvSearch.Tag.ToString();
                hlnkAdvSearch.Tag = Aux;

            }
            else
            {
                advanced.MainKeywords = this.txtQuery.Text;
            }
            SearcherFnc();
        }

        #endregion

        #region UI Methods
        void txtQueryKeyDown(object sender, KeyEventArgs e)
        {
            newSearch = true;
            actualPage = 1;
            totalPages = 1;
            totalItems = 0;
            if (e.Key == System.Windows.Input.Key.Enter)
            {
                if (e.Key == System.Windows.Input.Key.Enter)
                {
                    advanced.MainKeywords = this.txtQuery.Text;
                    advanced.IsAdvanced = false;
                    SearcherFnc();
                }

            }
        }

        void ShowItemInformation(object sender, MouseButtonEventArgs e)
        {
            /*
             * The event SelectionChanged is executed before the event ShowItemInformation,
             * so at this moment we don't know which item contain the selected photo,
             * and for this reason here we simulate the event SelectionChanged.
             */
            showItemInfo = true;
            lstResultSelectionChanged(sender, null);
        }

        void lstResultSelectionChanged(object sender, SelectionChangedEventArgs e)
        {
            List<Item> lst = new List<Item>();
            lst.Add((Item)lstResult.SelectedItem);
            icMoreInfoPopUp.ItemsSource = (IEnumerable<Item>)lst;
            if (showItemInfo)
            {
                PopUpLoading.Visibility = Visibility.Collapsed;
                PopUpBox.Visibility = Visibility.Visible;
                SignInPopUp.Visibility = Visibility.Collapsed;
                icMoreInfoPopUp.Visibility = Visibility.Visible;
                Popup();
                Show();                
                SBRotate.Completed += (s, ev) =>
                {
                    SBRotate.Stop();
                };
                SBRotate.Begin();
                showItemInfo = false;
            }
        }

        private void btnBooks_Click(object sender, RoutedEventArgs e)
        {
            if ((renderBigger.GetCurrentState() == ClockState.Active)
                || (renderLower.GetCurrentState() == ClockState.Active))
            {
                renderBigger.Stop();
                renderLower.Stop();
            }
            else
            {
                renderBigger.Begin();
            }
        }

        void btnAbout1BeginRotation(object sender, EventArgs args)
        {
            SBQuest1.Begin();
        }

        void btnAbout1StopRotation(object sender, EventArgs args)
        {
            SBQuest1.Stop();
        }

        void btnAbout2BeginRotation(object sender, EventArgs args)
        {
            SBQuest2.Begin();
        }

        void btnAbout2StopRotation(object sender, EventArgs args)
        {
            SBQuest2.Stop();
        }
        
        void Advanced(object sender, EventArgs args)
        {
            if (uctrlAdvSearch.Visibility == Visibility.Visible)
            {
                uctrlAdvSearch.Visibility = Visibility.Collapsed;
                txtQuery.Visibility = Visibility.Visible;
                btnCloseMessage_Click(sender, null);
                advanced.IsAdvanced = false;
                txtQuery.Focus();
                if (lstResult.Items.Count > 0)
                {
                    SearcherFnc();
                    InformationVisbility(true);
                }
            }
            else
            {
                InformationVisbility(false);
                if (sender.GetType().Equals(hlnkAdvSearch.GetType()))
                {
                    uctrlAdvSearch.Visibility = Visibility.Visible;
                    txtQuery.Visibility = Visibility.Collapsed;
                    advanced.IsAdvanced = true;
                    uctrlAdvSearch.SetFocus();
                }
            }

            string Aux = ((string)hlnkAdvSearch.Content);
            hlnkAdvSearch.Content = hlnkAdvSearch.Tag.ToString();
            hlnkAdvSearch.Tag = Aux;


        }

        private void InformationVisbility(Boolean visible)
        {
            if (visible)
            {
                lstResult.Visibility = Visibility.Visible;
                lstResult.Visibility = Visibility.Visible;
                txtPagesInfoT.Visibility = Visibility.Visible;
                hlkFPageT.Visibility = Visibility.Visible;
                hlkPPageT.Visibility = Visibility.Visible;
                hlkNPageT.Visibility = Visibility.Visible;
                hlkLPageT.Visibility = Visibility.Visible;

                txtPagesInfoB.Visibility = Visibility.Visible;
                hlkFPageB.Visibility = Visibility.Visible;
                hlkPPageB.Visibility = Visibility.Visible;
                hlkNPageB.Visibility = Visibility.Visible;
                hlkLPageB.Visibility = Visibility.Visible;
            }
            else
            {
                lstResult.Visibility = Visibility.Collapsed;
                txtPagesInfoT.Visibility = Visibility.Collapsed;
                hlkFPageT.Visibility = Visibility.Collapsed;
                hlkPPageT.Visibility = Visibility.Collapsed;
                hlkNPageT.Visibility = Visibility.Collapsed;
                hlkLPageT.Visibility = Visibility.Collapsed;

                txtPagesInfoB.Visibility = Visibility.Collapsed;
                hlkFPageB.Visibility = Visibility.Collapsed;
                hlkPPageB.Visibility = Visibility.Collapsed;
                hlkNPageB.Visibility = Visibility.Collapsed;
                hlkLPageB.Visibility = Visibility.Collapsed;
            }
        }

        private void hlkSignIn_Click(object sender, RoutedEventArgs e)
        {
            
            recKey.Visibility = Visibility.Visible;
            SBKey.Begin();

            //Clean the Error Message
            txtMsgKeyPopUp.Text = "";
            
            // Create thread to perform the key validation
            Thread worker = new Thread(new ThreadStart(CheckQuery));
            worker.Start();
        }
        
        private void CheckQuery(){
            // Set the manual reset
            Alldone = new ManualResetEvent(false);
            
            // Build the REST request            
            StringBuilder baseURL = new StringBuilder("http://ecs.amazonaws.com/onca/xml?Service=AWSECommerceService&Operation=ItemSearch&AWSAccessKeyId=").Append(RepInvalidChars(passwordAmazon)).Append("&SearchIndex=Books&ResponseGroup=Medium&Keywords=harry");
            RestDataAccess da = new RestDataAccess(baseURL.ToString());
            da.RestRequestCompleted += new EventHandler<RestRequestCompletedEventArgs>(da_RestRequestCompleted);
            da.PerformRestRequest();

            Alldone.WaitOne();

            //Invoque the event on the UiThread
            _mainDispatcher.BeginInvoke(delegate()
            {
                KeyValidationCompleted(validKey);
            });
        }

        private void KeyValidationCompleted(bool isKeyValid)
        {
            SBKey.Stop();
            recKey.Visibility = Visibility.Collapsed;
            if (isKeyValid)
            {
                hlkSignIn.Tag = passwordAmazon;
                SBLoad.Pause();
                btnCloseMessage_Click(null, null);
                SBLoad.Stop();
            }
            else
            {
                txtMsgKeyPopUp.Text = txtMsgKeyPopUp.Tag.ToString();
                txtKeyPopUp.Text = "";
                passwordAmazon = "";
            }
        }

        // Parse key validation response and set the key state (true or false)
        private void da_RestRequestCompleted(object sender, RestRequestCompletedEventArgs e)
        {
            //Handle the Key query result
            try
            {
                XmlReader xmlReader = XmlReader.Create(new StringReader(e.Result));

                XmlSerializer xSerializer = new XmlSerializer(typeof(Common.DataTypes.AmazonKeyQueryParser));

                Common.DataTypes.AmazonKeyQueryParser queryParser = (AmazonKeyQueryParser)xSerializer.Deserialize(xmlReader);

                // Set if the key is valid or not
                validKey = queryParser.IsValidKey();

                Alldone.Set();
            }
            catch (InvalidOperationException ex)
            {
                lblExcep.Text = ex.Message;
                PopUpLoading.Visibility = Visibility.Collapsed;
                PopUpKey.Visibility = Visibility.Collapsed;
                PopUpBox.Visibility = Visibility.Collapsed;
                PopUpExcep.Visibility = Visibility.Visible;
                Popup();
                Show();                
            }
        }

        private void hlkSignInAgain_Click(object sender, RoutedEventArgs e)
        {
            txtMsgKeyPopUp.Text = "";
            txtKeyPopUp.Text = passwordAmazon;
            txtKeyPopUp.SelectionStart = 1;
            
            PopUpKey.Visibility = Visibility.Visible;
            PopUpKeyContent.Visibility = Visibility.Visible;
            btnKeyClose.Visibility = Visibility.Visible;
            PopUpBox.Visibility = Visibility.Collapsed;
            SignInPopUp.Visibility = Visibility.Visible;
            Popup();
            Show();

            txtKeyPopUp.Focus();
        }
        #endregion

        #region Language

        void ChangeLanguage(object sender, EventArgs args)
        {            
            language = (language == 1) ? 2 : 1;
            textL.IdentifyLanguage = language;
            SetLanguage();
            if (lstResult.Visibility == Visibility.Visible)
            {
                SearcherFnc();
            }
        }
        
        private void SetLanguage()
        {
            hlkSignIn.Content = textL.GetText(Field.KeyChangeUsed);
            btnSearch.Content = textL.GetText(Field.Search);

            if (uctrlAdvSearch.Visibility == Visibility.Visible)
            {
                hlnkAdvSearch.Content = textL.GetText(Field.LinkSearchBasic);
                hlnkAdvSearch.Tag = textL.GetText(Field.LinkSearchAdvanced);
            }
            else
            {                
                hlnkAdvSearch.Content = textL.GetText(Field.LinkSearchAdvanced);
                hlnkAdvSearch.Tag = textL.GetText(Field.LinkSearchBasic);
            }
            
            txtAmazonKeyPopUp.Text = textL.GetText(Field.KeyTitle);
            hlkSignInPopUp.Content = textL.GetText(Field.KeySignIn);

            //Paginated - of
            txtPagesInfoB.Tag = textL.GetText(Field.PaginatedPageOf);
            if (txtPagesInfoT.Tag != null)
            {
                txtPagesInfoT.Text = ((string)txtPagesInfoT.Tag).Replace("[p]", txtPagesInfoB.Tag.ToString());
                txtPagesInfoB.Text = txtPagesInfoT.Text;
            }

            // It shows the appropriate photo
            imgEEUU.Visibility = (language == 2) ? Visibility.Visible : Visibility.Collapsed;
            imgES.Visibility = (language == 1) ? Visibility.Visible : Visibility.Collapsed;

            //Loading
            lblLoading.Text = textL.GetText(Field.SearchLoading);

            //Invalid key
            txtMsgKeyPopUp.Tag = textL.GetText(Field.InvalidKey);

            //Advanced Search
            uctrlAdvSearch.SetLanguage(language);
        }        

        #endregion
        
        #region Password

        /// <summary>
        /// Method used by regexp, to delete ilegal characters in password string
        /// </summary>
        /// <returns></returns>
        private static string Rep()
        {
            return "*";
        }
        
        /// <summary>
        /// Delete ilegal characters in password strings
        /// </summary>
        /// <param name="s"></param>
        /// <returns></returns> 
        private static string RepInvalidChars(string s)
        {
            string res;
            string sRegex = @"\W";
            Regex r = new Regex(sRegex);
            res = r.Replace(s, Rep());            
            return res;
        }

        void txtKey_KeyDown(object sender, KeyEventArgs args)
        {
            if (args.Key == System.Windows.Input.Key.Enter)
            {
                hlkSignIn_Click(null, null);
            }
        }
        
        void txtKey_TextChanged(object sender, TextChangedEventArgs args)
        {
            if (passwordChanged)
            {
                if (SignInPopUp.Visibility == Visibility.Visible)
                {
                    int Index = txtKeyPopUp.SelectionStart;

                    int Rest = txtKeyPopUp.Text.Length - passwordAmazon.Length;

                    if (Rest > 0)
                    {
                        passwordAmazon = passwordAmazon.Insert(txtKeyPopUp.SelectionStart - Rest, txtKeyPopUp.Text.Substring(txtKeyPopUp.SelectionStart - Rest, Rest));
                    }
                    else if (Rest == 0)
                    {
                        if (passwordAmazon.Length > 0)
                        {
                            passwordAmazon = passwordAmazon.Substring(0, txtKeyPopUp.SelectionStart - 1)
                                          + txtKeyPopUp.Text.Substring(txtKeyPopUp.SelectionStart - 1, 1)
                                          + passwordAmazon.Substring(txtKeyPopUp.SelectionStart, passwordAmazon.Length - txtKeyPopUp.SelectionStart);
                        }
                    }
                    else
                    {
                        Rest = Rest * -1;
                        passwordAmazon = passwordAmazon.Remove(txtKeyPopUp.SelectionStart, Rest);                    
                    }

                    
                    string Aux = txtKeyPopUp.Text;
                    txtKeyPopUp.Text = new string('*', txtKeyPopUp.Text.Length);
                    if (Aux != txtKeyPopUp.Text)
                    {
                        passwordChanged = false;
                    }
                    txtKeyPopUp.SelectionStart = Index;                
                }
            }
            else
            {
                passwordChanged = true;
            }
        }

        private void txtKeyPopUp_GotFocus(object sender, RoutedEventArgs e)
        {
            txtKeyPopUp.SelectionStart = 0;
            txtKeyPopUp.SelectionLength = txtKeyPopUp.Text.Length;
        }

        #endregion
        
        #region Paginated

        private void InitializePagesInformation()
        {
            if (totalItems == 0)
            {
                txtPagesInfoT.Text = textL.GetText(Field.PaginatedPageNoResult);

                // Hide text of number of results
                txtPagesInfoT.Visibility = Visibility.Visible;
                txtPagesInfoB.Visibility = Visibility.Collapsed;

                // Hide navigation buttons
                this.hideNavigationButtons();
            }
            else
            {
                actualPage = 1;

                if (totalItems <= ITEMS_PER_PAGE)
                {
                    totalPages = 1;
                    RefreshTxtPages(1, totalItems);

                    txtPagesInfoT.Visibility = Visibility.Visible;
                    txtPagesInfoB.Visibility = Visibility.Visible;

                    // Hide navigation buttons
                    this.hideNavigationButtons();
                }
                else
                {
                    if (totalItems > 100)
                    {
                        totalItems = 100;
                    }

                    totalPages = Convert.ToInt32(Math.Ceiling(Convert.ToDouble(totalItems) / ITEMS_PER_PAGE));

                    RefreshTxtPages(1, ITEMS_PER_PAGE);

                    txtPagesInfoT.Visibility = Visibility.Visible;
                    hlkFPageT.Visibility = Visibility.Collapsed;
                    hlkPPageT.Visibility = Visibility.Collapsed;
                    hlkNPageT.Visibility = Visibility.Visible;
                    hlkLPageT.Visibility = Visibility.Visible;

                    txtPagesInfoB.Visibility = Visibility.Visible;
                    hlkFPageB.Visibility = Visibility.Collapsed;
                    hlkPPageB.Visibility = Visibility.Collapsed;
                    hlkNPageB.Visibility = Visibility.Visible;
                    hlkLPageB.Visibility = Visibility.Visible;
                }
            }
        }

        private void hideNavigationButtons()
        {
            // Hide all navigation buttons
            hlkFPageT.Visibility = Visibility.Collapsed;
            hlkPPageT.Visibility = Visibility.Collapsed;
            hlkNPageT.Visibility = Visibility.Collapsed;
            hlkLPageT.Visibility = Visibility.Collapsed;

            hlkFPageB.Visibility = Visibility.Collapsed;
            hlkPPageB.Visibility = Visibility.Collapsed;
            hlkNPageB.Visibility = Visibility.Collapsed;
            hlkLPageB.Visibility = Visibility.Collapsed;
        }

        private void hlkFPage_Click(object sender, RoutedEventArgs e)
        {
            newSearch = false;
            actualPage = 1;
            SearcherFnc();

            // Calculate the last item of the first page. It's the lower between ITEMS_PER_PAGE and the number of items of the result
            int to = Convert.ToInt32(Math.Min(ITEMS_PER_PAGE, totalItems));

            RefreshTxtPages(1, to);

            hlkFPageT.Visibility = Visibility.Collapsed;
            hlkPPageT.Visibility = Visibility.Collapsed;
            hlkNPageT.Visibility = Visibility.Visible;
            hlkLPageT.Visibility = Visibility.Visible;

            hlkFPageB.Visibility = Visibility.Collapsed;
            hlkPPageB.Visibility = Visibility.Collapsed;
            hlkNPageB.Visibility = Visibility.Visible;
            hlkLPageB.Visibility = Visibility.Visible;
        }
        
        private void hlkPPage_Click(object sender, RoutedEventArgs e)
        {
            newSearch = false;
            actualPage -= 1;
            SearcherFnc();

            int from = ((actualPage - 1) * ITEMS_PER_PAGE) + 1;
            int to = actualPage * ITEMS_PER_PAGE;

            hlkNPageT.Visibility = Visibility.Visible;
            hlkLPageT.Visibility = Visibility.Visible;
            hlkNPageB.Visibility = Visibility.Visible;
            hlkLPageB.Visibility = Visibility.Visible;

            if (actualPage == 1)
            {
                hlkFPageT.Visibility = Visibility.Collapsed;
                hlkPPageT.Visibility = Visibility.Collapsed;
                hlkFPageB.Visibility = Visibility.Collapsed;
                hlkPPageB.Visibility = Visibility.Collapsed;
            }

            RefreshTxtPages(from, to);
        }

        private void hlkNPage_Click(object sender, RoutedEventArgs e)
        {
            newSearch = false;
            actualPage += 1;
            SearcherFnc();

            int from = ((actualPage - 1) * ITEMS_PER_PAGE) + 1;
            int to = actualPage * ITEMS_PER_PAGE;

            hlkFPageT.Visibility = Visibility.Visible;
            hlkPPageT.Visibility = Visibility.Visible;
            hlkFPageB.Visibility = Visibility.Visible;
            hlkPPageB.Visibility = Visibility.Visible;

            if (actualPage == totalPages)
            {
                to = totalItems;
                hlkNPageT.Visibility = Visibility.Collapsed;
                hlkLPageT.Visibility = Visibility.Collapsed;
                hlkNPageB.Visibility = Visibility.Collapsed;
                hlkLPageB.Visibility = Visibility.Collapsed;
            }

            RefreshTxtPages(from, to);
        }

        private void hlkLPage_Click(object sender, RoutedEventArgs e)
        {
            newSearch = false;
            actualPage = totalPages;
            SearcherFnc();

            int from = ((actualPage - 1) * ITEMS_PER_PAGE) + 1;
            int to = from + ((totalItems - 1) % ITEMS_PER_PAGE);

            hlkFPageT.Visibility = Visibility.Visible;
            hlkPPageT.Visibility = Visibility.Visible;
            hlkFPageB.Visibility = Visibility.Visible;
            hlkPPageB.Visibility = Visibility.Visible;

            hlkNPageT.Visibility = Visibility.Collapsed;
            hlkLPageT.Visibility = Visibility.Collapsed;
            hlkNPageB.Visibility = Visibility.Collapsed;
            hlkLPageB.Visibility = Visibility.Collapsed;

            RefreshTxtPages(from, to);
        }

        private void RefreshTxtPages(int from, int to)
        {
            txtPagesInfoT.Tag = " " + from.ToString(CultureInfo.CurrentCulture) + "-" + to.ToString(CultureInfo.CurrentCulture) + " " +
                                 "[p]" + " " + totalItems.ToString(CultureInfo.CurrentCulture) + " ";

            txtPagesInfoT.Text = ((string)txtPagesInfoT.Tag).Replace("[p]", txtPagesInfoB.Tag.ToString());
            txtPagesInfoB.Text = txtPagesInfoT.Text;
        }

        #region First,Previous,Next,Last
        
        private void hlkPage_MouseEnter(object sender, MouseEventArgs e)
        {
            switch (((Button)sender).Name)
            {
                case "hlkFPageT":
                    imgFirstT.Source = new BitmapImage(new Uri("images/First.jpg", UriKind.RelativeOrAbsolute));
                    break;
                case "hlkPPageT":
                    imgPreviousT.Source = new BitmapImage(new Uri("images/Previous.jpg", UriKind.RelativeOrAbsolute));
                    break;
                case "hlkNPageT":
                    imgNextT.Source = new BitmapImage(new Uri("images/Next.jpg", UriKind.RelativeOrAbsolute));
                    break;
                case "hlkLPageT":
                    imgLastT.Source = new BitmapImage(new Uri("images/Last.jpg", UriKind.RelativeOrAbsolute));
                    break;
                case "hlkFPageB":
                    imgFirstB.Source = new BitmapImage(new Uri("images/FirstT.jpg", UriKind.RelativeOrAbsolute));
                    break;
                case "hlkPPageB":
                    imgPreviousB.Source = new BitmapImage(new Uri("images/PreviousT.jpg", UriKind.RelativeOrAbsolute));
                    break;
                case "hlkNPageB":
                    imgNextB.Source = new BitmapImage(new Uri("images/NextT.jpg", UriKind.RelativeOrAbsolute));
                    break;
                case "hlkLPageB":
                    imgLastB.Source = new BitmapImage(new Uri("images/LastT.jpg", UriKind.RelativeOrAbsolute));
                    break;
            }
        }

        private void hlkPage_MouseLeave(object sender, MouseEventArgs e)
        {
            switch (((Button)sender).Name)
            {
                case "hlkFPageT":
                    imgFirstT.Source = new BitmapImage(new Uri("images/FirstT.jpg", UriKind.RelativeOrAbsolute));
                    break;
                case "hlkPPageT":
                    imgPreviousT.Source = new BitmapImage(new Uri("images/PreviousT.jpg", UriKind.RelativeOrAbsolute));
                    break;
                case "hlkNPageT":
                    imgNextT.Source = new BitmapImage(new Uri("images/NextT.jpg", UriKind.RelativeOrAbsolute));
                    break;
                case "hlkLPageT":
                    imgLastT.Source = new BitmapImage(new Uri("images/LastT.jpg", UriKind.RelativeOrAbsolute));
                    break;
                case "hlkFPageB":
                    imgFirstB.Source = new BitmapImage(new Uri("images/First.jpg", UriKind.RelativeOrAbsolute));
                    break;
                case "hlkPPageB":
                    imgPreviousB.Source = new BitmapImage(new Uri("images/Previous.jpg", UriKind.RelativeOrAbsolute));
                    break;
                case "hlkNPageB":
                    imgNextB.Source = new BitmapImage(new Uri("images/Next.jpg", UriKind.RelativeOrAbsolute));
                    break;
                case "hlkLPageB":
                    imgLastB.Source = new BitmapImage(new Uri("images/Last.jpg", UriKind.RelativeOrAbsolute));
                    break;
            }
        }
        #endregion

        #endregion

        #region PopUp

        public void Popup()
        {
            App.Current.Host.Content.Resized += new EventHandler(Content_Resized);
            backGround.Width = LayoutRoot.ActualWidth;
            backGround.Height = LayoutRoot.ActualHeight;
        }

        void Content_Resized(object sender, EventArgs e)
        {
            backGround.Width = LayoutRoot.ActualWidth;
            backGround.Height = LayoutRoot.ActualHeight;
        }


        void btnCloseMessage_Click(object sender, RoutedEventArgs e)
        {
            closeMessage.Completed += (s, ev) =>
            {
                openMessage.Stop();
                closeMessage.Stop();
            };
            closeMessage.Begin();
            PopUpExcep.Visibility = Visibility.Collapsed;
            PopUpKeyContent.Visibility = Visibility.Collapsed;
            BaseLayoutRoot.Visibility = Visibility.Visible;
            BrdLayoutRoot.Visibility = Visibility.Visible;
            SBRotate.Begin();
            SBRotate.Completed += (s, ev) =>
            {
                SBRotate.Stop();
            };
            txtQuery.Focus();
        }

        void btnLoadingMessage_Click(object sender, RoutedEventArgs e)
        {
            closeMessage.Completed += (s, ev) =>
            {
                openMessage.Stop();
                closeMessage.Stop();
            };
            closeMessage.Begin();
            PopUpExcep.Visibility = Visibility.Collapsed;
            PopUpKeyContent.Visibility = Visibility.Collapsed;
            BaseLayoutRoot.Visibility = Visibility.Visible;
            BrdLayoutRoot.Visibility = Visibility.Visible;

            txtQuery.Focus();
        }

        void btnKeyClose_Click(object sender, RoutedEventArgs e)
        {
            passwordAmazon = hlkSignIn.Tag.ToString();
            closeMessage.Begin();
            PopUpKeyContent.Visibility = Visibility.Collapsed;
            BaseLayoutRoot.Visibility = Visibility.Visible;
            BrdLayoutRoot.Visibility = Visibility.Visible;

            txtQuery.Focus();
        }

        public void Close()
        {
            popUpMessage.IsOpen = false;
            backGround.Visibility = Visibility.Collapsed;
        }

        public void Show()
        {
            Point p = new Point();

            if (PopUpBox.Visibility == Visibility.Visible)
            {
                p.X = App.Current.Host.Content.ActualWidth / 4;
                p.Y = (App.Current.Host.Content.ActualHeight / 2);
                if (p.Y > 150)
                {
                    //This is to prevent that the PopUpBox size is bigger than the visible section
                    p.Y = p.Y - 150;
                }
                scrlGral.ScrollToVerticalOffset(p.Y / 2);
                icMoreInfoPopUp.Focus();
                PopUpBox.Margin = new Thickness(p.X, p.Y, 0, 0);
            }
            if (PopUpKey.Visibility == Visibility.Visible)
            {
                p.X = App.Current.Host.Content.ActualWidth / 3;
                p.Y = App.Current.Host.Content.ActualHeight / 3;
                PopUpKey.Margin = new Thickness(p.X, p.Y, 0, 0);
            }
            if (PopUpLoading.Visibility == Visibility.Visible)
            {
                p.X = App.Current.Host.Content.ActualWidth / 3;
                p.Y = App.Current.Host.Content.ActualHeight / 3;
                PopUpLoading.Margin = new Thickness(p.X, p.Y, 0, 0);
            }
            if (PopUpExcep.Visibility == Visibility.Visible)
            {
                p.X = App.Current.Host.Content.ActualWidth / 3;
                p.Y = (App.Current.Host.Content.ActualHeight / 2);
                if (p.Y > 150)
                {
                    //This is to prevent that the PopUpBox size is bigger than the visible section
                    p.Y = p.Y - 150;
                }
                scrlGral.ScrollToVerticalOffset(p.Y / 2);
                PopUpExcep.Margin = new Thickness(p.X, p.Y, 0, 0);
            }

            popUpMessage.IsOpen = true;
            backGround.Visibility = Visibility.Visible;
            openMessage.Completed += (s, e) =>
            {
                btnCloseMessage.Focus();
            };
            openMessage.Begin();
        }


        #endregion

        private void ResultSearch_Loaded(object sender, RoutedEventArgs e)
        {            
            TextBlock lblAux = ((TextBlock)sender);
            lblAux.Text = textL.GetTextItemResult(lblAux.Name);
        }

        //To perform the search from any field of the Advanced Search
        private void uctrlAdvSearch_KeyUp(object sender, KeyEventArgs e)
        {
            if (Key.Enter == e.Key)
            {                
                Search_Click(null, null);
            }
        }

    }

}
